﻿using System;
using System.Collections.Generic;
using GeoAPI.Geometries;
using YJKGridTopologyCal.Algorithm;
using YJKGridTopologyCal.GeometriesGraph;
using YJKGridTopologyCal.Index;
using YJKGridTopologyCal.Index.Strtree;

namespace YJKGridTopologyCal.Operation.Valid
{
	public class IndexedNestedRingTester
	{
		public IndexedNestedRingTester(GeometryGraph graph)
		{
			this._graph = graph;
		}

		public Coordinate NestedPoint
		{
			get
			{
				return this._nestedPt;
			}
		}

		public void Add(ILinearRing ring)
		{
			this._rings.Add(ring);
			this._totalEnv.ExpandToInclude(ring.EnvelopeInternal);
		}

		public bool IsNonNested()
		{
			this.BuildIndex();
			for (int i = 0; i < this._rings.Count; i++)
			{
				ILinearRing linearRing = (ILinearRing)this._rings[i];
				Coordinate[] coordinates = linearRing.Coordinates;
				IList<ILineString> list = this._index.Query(linearRing.EnvelopeInternal);
				for (int j = 0; j < list.Count; j++)
				{
					ILinearRing linearRing2 = (ILinearRing)list[j];
					Coordinate[] coordinates2 = linearRing2.Coordinates;
					if (linearRing != linearRing2 && linearRing.EnvelopeInternal.Intersects(linearRing2.EnvelopeInternal))
					{
						Coordinate coordinate = IsValidOp.FindPointNotNode(coordinates, linearRing2, this._graph);
						if (coordinate != null && CGAlgorithms.IsPointInRing(coordinate, coordinates2))
						{
							this._nestedPt = coordinate;
							return false;
						}
					}
				}
			}
			return true;
		}

		private void BuildIndex()
		{
			this._index = new STRtree<ILineString>();
			for (int i = 0; i < this._rings.Count; i++)
			{
				ILinearRing linearRing = (ILinearRing)this._rings[i];
				Envelope envelopeInternal = linearRing.EnvelopeInternal;
				this._index.Insert(envelopeInternal, linearRing);
			}
		}

		private readonly GeometryGraph _graph;

		private readonly IList<ILineString> _rings = new List<ILineString>();

		private readonly Envelope _totalEnv = new Envelope();

		private ISpatialIndex<ILineString> _index;

		private Coordinate _nestedPt;
	}
}
